package com.googlecode.curvedmetromaps.core.logic.forcedriven;

import org.jbox2d.common.Vec2;
import org.jbox2d.dynamics.Body;

import com.googlecode.curvedmetromaps.core.model.MetroEdge;

/**
 * Constraint S5: minimizes total arc length.
 */
public class ForceAttracktiveStations extends ForceSubsystem {
	public ForceWeight adjDist = new ForceWeight("Adjacent distance", 1);
	
	ForceAttracktiveStations(ForceSystem system) {
		super(system);
		baseWeight.value = 1500;
	}

	void applyForces(int delta) {
		applyEdgeAttractiveForces(delta);
	}

	private void applyEdgeAttractiveForces(int delta) {
		for (MetroEdge edge : system.metroMap.edgeArray) {
			Body m1body = system.stationBodies[edge.src.id];
			Body m2body = system.stationBodies[edge.dst.id];
			Vec2 p1 = m1body.getPosition();
			Vec2 p2 = m2body.getPosition();

			Vec2 direction = p1.sub(p2);
			float len = direction.normalize();
			
			float minLength = 0.001f;
			if (len < minLength) len = minLength;
			double f = baseWeight.value * Math.log(len / adjDist.value);

			direction.mulLocal((float) f);

			m2body.applyForceToCenter(direction);
			m1body.applyForceToCenter(direction.negateLocal());
		}
	}
}
